package concurrencyPractice.chapter05;

import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.FutureTask;

/**
 * @author xinya
 * @version 1.0
 * @project javacore
 * @description 程序5-12 使用 FutureTask 提前加载稍后需要的数据
 * @date 2024/1/2 15:29:10
 */
public class Preloader<ProductInfo> {
    private final FutureTask<ProductInfo> future = new FutureTask<ProductInfo>(new Callable<ProductInfo>() {
        @Override
        public ProductInfo call() throws Exception {
            return loadProductInfo();
        }
    });

    private final ProductInfo loadProductInfo() {
        return null;
    }

    private final Thread thread = new Thread(future);

    public ProductInfo get() throws DataLoadException, InterruptedException {
        try {
            return future.get();
        } catch (ExecutionException e) {
            Throwable cause = e.getCause();
            if (cause instanceof DataLoadException) {
                throw (DataLoadException) cause;
            } else {
                throw launderThrowable(cause);
            }
        }
    }

    /**
     * 程序5-13 强制将未检查的 Throwable 转化为 RuntimeException
     *
     * @param t
     * @return
     */
    public static RuntimeException launderThrowable(Throwable t) {
        if (t instanceof RuntimeException) {
            return (RuntimeException) t;
        } else if (t instanceof Error) {
            throw (Error) t;
        } else
            throw new IllegalStateException("not checked", t);
    }
}

class DataLoadException extends Throwable {

}